package com.example.admindatasource.service.impl;

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.ExcelReader;
import com.alibaba.excel.read.builder.ExcelReaderBuilder;
import com.alibaba.excel.read.metadata.ReadSheet;
import com.example.admindatasource.constant.ModelFileConstant;
import com.example.admindatasource.exception.FileException;
import com.example.admindatasource.filepload.FileConstant;
import com.example.admindatasource.model.bo.ModelStructureBO;
import com.example.admindatasource.model.bo.ModelStructureExtBO;
import com.example.admindatasource.model.po.SysUploadFile;
import com.example.admindatasource.model.vo.DataAndStructVO;
import com.example.admindatasource.model.vo.SysUploadFileVO;
import com.example.admindatasource.service.ISysUploadFileService;
import com.example.admindatasource.service.IVitalModelFileService;
import com.example.adminframework.constant.ErrorCode;
import com.example.adminframework.constant.HttpCode;
import com.sun.javaws.CacheUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.*;
import java.util.stream.Collectors;

import static org.springframework.beans.support.PagedListHolder.DEFAULT_PAGE_SIZE;

@Service
public class IVitalModelFileServiceImpl implements IVitalModelFileService {


    @Autowired
    private ISysUploadFileService sysUploadFileService;


    /**
     * 文件上传
     * @param file      文件
     * @param request   请求
     * @return
     */
    @Override
    public DataAndStructVO fileUpload(MultipartFile file, HttpServletRequest request) {
        if (ObjectUtils.isEmpty(file)){
            throw new FileException(HttpCode.BAD_REQUEST, ErrorCode.NON_PARAMETRIC);
        }
        List<Map<String, Object>> excelSheetInfo = getExcelSheetInfo(file);
        // 生成唯一标识
        String uuid = UUID.randomUUID().toString();
        SysUploadFileVO sysUploadFileVO = sysUploadFileService.fileUpload("default", file);
        // 将UUID存入session中 方便解析时直接获取
        request.getSession().setAttribute(ModelFileConstant.DATA_MODEL_MANAGE_FILE_SESSION_KEY, uuid);
        DataAndStructVO dataAndStructVO = new DataAndStructVO();
        dataAndStructVO.setUuid(uuid);
        dataAndStructVO.setSheetList(excelSheetInfo);
        return dataAndStructVO;
    }



    @Override
    public DataAndStructVO preprocess(Integer startRow, HttpServletRequest request) {

        return null;
    }


    /**
     * 检查是否有相同的列
     */
    private void checkFieldRepeat(List<ModelStructureExtBO> structureExtBOS) {
        Set<String> set = structureExtBOS.stream().map(ModelStructureBO::getField).collect(Collectors.toSet());
        if (set.size() < structureExtBOS.size()) {
//            说明存在重复字段
            throw new FileException(HttpCode.BAD_REQUEST, ErrorCode.MODEL_FILE_HEADER_REPETITION);
        }
    }

    /**
     *  获取文件Sheet信息
     *  @param file
     */
    private List<Map<String,Object>> getExcelSheetInfo(MultipartFile file){
        // 目前只支持excel取Sheet页，CSV文件无Sheet页概念
        String originalFilename = file.getOriginalFilename();
        String fileSuffix = originalFilename.substring(originalFilename.lastIndexOf(".") + 1);
        // 获取对应文件Sheet信息
        if ("xlsx".equals(fileSuffix) || "xls".equals(fileSuffix)) {
            // 获取输入流
            InputStream inputStream = null;
            List<ReadSheet> sheets = null;
            try {
                inputStream = file.getInputStream();
                ExcelReaderBuilder excelReaderBuilder = EasyExcel.read(inputStream);
                ExcelReader excelReader = excelReaderBuilder.build();
                // 获取Sheet相关信息
                sheets = excelReader.excelExecutor().sheetList();
            } catch (IOException e) {
                e.printStackTrace();
            }finally {
                // 关闭流
                try {
                    inputStream.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            // 收集结果
            List<Map<String,Object>> result = sheets.stream().map(sheet -> {
                Map<String, Object> map = new HashMap<>();
                map.put("sheetName", sheet.getSheetName());
                map.put("sheetNo", sheet.getSheetNo());
                return map;
            }).collect(Collectors.toList());
            return result;
        }
        return new ArrayList<>();
    }


}
